package com.py.credit.controller;

import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Date;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.CollectionUtils;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;

import com.alibaba.fastjson.JSONArray;
import com.py.credit.common.logs.ExceptionLogger;
import com.py.credit.common.rest.RestServiceResult;
import com.py.credit.entity.SysUser;
import com.py.credit.entity.common.InspectRule;
import com.py.credit.entity.common.OptionalColumn;
import com.py.credit.entity.enums.ResourceColumnRuleFieldsEnum;
import com.py.credit.entity.enums.ResourceColumnRuleFieldsEnum2;
import com.py.credit.service.ColumnRuleService;
import com.py.credit.service.RemoteBaseService;
import com.py.credit.service.RuleBindingService;
import com.py.credit.utils.ExcelUtil;
import com.py.credit.utils.MapCache;
import com.py.framework.core.annotation.IgnoreAuthority;
import com.py.framework.core.common.Page;
import com.py.framework.core.helper.HttpServletHelper;

@RestController
@RequestMapping(value = "/columnRule")
public class ColumnRuleController {

	private final static String FRONT_TABLE_ID = "columnRule";

	@Autowired
	private ColumnRuleService columnRuleService;

	@Autowired
	private RemoteBaseService remoteBaseService;

	@Autowired
	private RuleBindingService ruleBindingService;

	/**
	 * 获取初始化列
	 * 
	 * @return
	 */
	@RequestMapping(value = "/getOptionalColums.json")
	public RestServiceResult<List<OptionalColumn>> getOptionalColums() {
		return new RestServiceResult<List<OptionalColumn>>(ResourceColumnRuleFieldsEnum.getOptionalColumns());
	}

	@RequestMapping(value = "/getAdvancedConditionColumns.json")
	public RestServiceResult<List<OptionalColumn>> getAdvancedConditionColumns() {
		return new RestServiceResult<List<OptionalColumn>>(ResourceColumnRuleFieldsEnum.getAdvancedConditionColumns());
	}
	
	
	@RequestMapping(value = "/getOptionalColums2.json")
	public RestServiceResult<List<OptionalColumn>> getOptionalColums2() {
		return new RestServiceResult<List<OptionalColumn>>(ResourceColumnRuleFieldsEnum2.getOptionalColumns());
	}

	@RequestMapping(value = "/getAdvancedConditionColumns2.json")
	public RestServiceResult<List<OptionalColumn>> getAdvancedConditionColumns2() {
		return new RestServiceResult<List<OptionalColumn>>(ResourceColumnRuleFieldsEnum2.getAdvancedConditionColumns());
	}
	
	@RequestMapping(value = "/export2")
	public RestServiceResult<Object> export2(
			@RequestParam(value = "condition", defaultValue = "", required = true) String condition,
			@RequestParam(value = "columnEN", defaultValue = "", required = true) String columnEN,
			@RequestParam(defaultValue = "", required = true, value = "filed_code") String filedCode,
			HttpServletResponse response, Page page, HttpServletRequest request) {
		page.setLimit(1000);
		List<String> columns = JSONArray.parseArray(columnEN, String.class);
		columns.add("managerId");
		RestServiceResult<Object> result = new RestServiceResult<Object>();
		try {
			List<Map<String, Object>> data = columnRuleService.getByConditionForPage(columns, null, condition, page,
					filedCode);
			if (!CollectionUtils.isEmpty(data)) {
				Set<Integer> userIds = new HashSet<Integer>();
				for (Map<String, Object> map : data) {
					if (null != map && null != map.get("managerId")) {
						userIds.add(Integer.parseInt(String.valueOf(map.get("managerId"))));
					}
				}
				if (!CollectionUtils.isEmpty(userIds)) {
					data = remoteBaseService.matchUserName(data, new RestServiceResult<List<Map<String, Object>>>(),
							HttpServletHelper.getUserToken(request), userIds, "managerId", "managerName");
					if (RestServiceResult.CODE_SUCCESS != result.getCode()) {
						return result;
					}
				}
			}
			ExcelUtil.downloadExcel(response, data, "字段规则信息", "字段规则信息", columns,
					ResourceColumnRuleFieldsEnum2.getOptionalColumns());
			return result;
		} catch (IOException e) {
			result.setCode(RestServiceResult.CODE_UNKNOW);
			result.setMsg("系统异常，请稍后再试！");
			ExceptionLogger.error("字段规则信息导出异常！", e.getMessage(), e);
			return result;
		}
	}

	/**
	 * @api {get} /columnRule/getTableList.json 获取字段规则列表
	 * @apiName getTableList
	 * @apiVersion 0.0.1
	 * @apiGroup 字段规则配置
	 * 
	 * @apiParam {String} condition 查询条件(可选)
	 * @apiParam {int} limit 每页展示条数 (必需)
	 * @apiParam {int} page 当前页数 (必需)
	 * 
	 * @apiSuccess {String} code 状态码:1 成功 -1 失败
	 * @apiSuccess {String} msg 错误信息
	 * @apiSuccess {int} count 结果集数据量
	 * @apiSuccess {Object[]} data 结果集
	 *
	 * @apiSuccessExample {json} 成功返回结果
	 *                    {"code":0,"msg":null,"count":2,"data":[{"rule_package":"1222","rule_desc":"122222","rule_name":"1","rule_method":"123","id":22,"time":"2018-04-23","managerName":"超级管理员"},{"rule_package":"555","rule_desc":"5555","rule_name":"555","rule_method":"555","id":35,"time":"2018-04-26","managerName":"超级管理员"}]}
	 * 
	 */
	@RequestMapping(value = "/getTableList.json")
	public RestServiceResult<List<Map<String, Object>>> getTableList(
			@RequestParam(value = "condition", defaultValue = "", required = true) String condition,
			@RequestParam(defaultValue = "", required = true, value = "filedId") String fieldId, Page page,
			HttpServletRequest request) {
		RestServiceResult<List<Map<String, Object>>> result = new RestServiceResult<List<Map<String, Object>>>();
		// 获取当前用户信息
		RestServiceResult<SysUser> user = remoteBaseService.getCurrentUser(HttpServletHelper.getUserToken(request));
		SysUser userInfo = null;
		if (RestServiceResult.CODE_SUCCESS == user.getCode()) {
			userInfo = user.getData();
			if (null == userInfo || userInfo.getId() <= 0) {
				result.setCode(RestServiceResult.CODE_UNKNOW);
				result.setMsg("系统异常，请稍后再试！");
				ExceptionLogger.error("ColumnRuleController#getTableList", "未获取到当前用户信息！");
				return result;
			}
		} else {
			result.setCode(user.getCode());
			result.setMsg(user.getMsg());
			return result;
		}
		String[] configColumns = (String[]) MapCache.get(userInfo.getId() + "_" + FRONT_TABLE_ID);
		List<String> showColumns = (configColumns == null || configColumns.length == 0)
				? ResourceColumnRuleFieldsEnum.getDefaultShowColumnEN() : Arrays.asList(configColumns);
		// condition="[{columnEN:\"batch_id\",value:\"EX-test-1-20180326-1174\",type:\"varchar\",fuzzy:fasle}]";
		try {
			List<Map<String, Object>> tableList = columnRuleService.getByConditionForPage(showColumns,
					new String[] { "bindingId", "id" }, condition, page, fieldId);
			if (!CollectionUtils.isEmpty(tableList)) {
				Set<Integer> userIds = new HashSet<Integer>();
				for (Map<String, Object> map : tableList) {
					if (null != map && null != map.get("managerId")) {
						userIds.add(Integer.parseInt(String.valueOf(map.get("managerId"))));
					}
				}
				if (!CollectionUtils.isEmpty(userIds)) {
					tableList = remoteBaseService.matchUserName(tableList, result,
							HttpServletHelper.getUserToken(request), userIds, "managerId", "managerName");
					if (RestServiceResult.CODE_SUCCESS != result.getCode()) {
						return result;
					}
				}
			}
			result.setCount(page.getTotalCount());
			result.setData(tableList);
			return result;
		} catch (Exception e) {
			result.setCode(RestServiceResult.CODE_UNKNOW);
			result.setMsg("系统异常，请稍后再试！");
			ExceptionLogger.error("获取字段规则列表异常！", e.getMessage(), e);
			return result;
		}
	}

	/**
	 * 手动选择展示列
	 * 
	 * @param columns
	 * @return
	 */
	@RequestMapping(value = "/addShowColunms.json")
	public RestServiceResult<String> addShowColunms(@RequestParam(value = "columns", required = true) String[] columns,
			HttpServletRequest request) {
		RestServiceResult<String> result = new RestServiceResult<String>();
		// 获取当前用户信息
		RestServiceResult<SysUser> user = remoteBaseService.getCurrentUser(HttpServletHelper.getUserToken(request));
		SysUser userInfo = null;
		if (RestServiceResult.CODE_SUCCESS == user.getCode()) {
			userInfo = user.getData();
			if (null == userInfo || userInfo.getId() <= 0) {
				result.setCode(RestServiceResult.CODE_UNKNOW);
				result.setMsg("系统异常，请稍后再试！");
				ExceptionLogger.error("ColumnRuleController#addShowColunms", "未获取到当前用户信息！");
				return result;
			}
		} else {
			result.setCode(user.getCode());
			result.setMsg(user.getMsg());
			return result;
		}
		String column = StringUtils.join(columns, ",");
		column = column + ",managerId";
		MapCache.set(userInfo.getId() + "_" + FRONT_TABLE_ID, StringUtils.split(column, ","));
		return new RestServiceResult<String>();
	}

	/**
	 * 
	 * @api {get} /columnRule/export.json 字段规则信息导出
	 * @apiName export
	 * @apiVersion 0.0.1
	 * @apiGroup 字段规则信息
	 * @apiParam {String} showColumn 导出字段数组
	 * @apiParamExample {json} 请求参数示例 {}
	 * @apiSuccess {String} code 状态码:1 成功 -1 失败
	 * @apiSuccess {String} msg 错误信息
	 * @apiSuccess {int} count 结果集数据量
	 * @apiSuccess {String} data 结果集
	 * @apiSuccessExample {json} 成功返回结果 {}
	 */
	@RequestMapping(value = "/export")
	public RestServiceResult<Object> export(
			@RequestParam(value = "condition", defaultValue = "", required = true) String condition,
			@RequestParam(value = "columnEN", defaultValue = "", required = true) String columnEN,
			@RequestParam(defaultValue = "", required = true, value = "filed_code") String filedCode,
			HttpServletResponse response, Page page, HttpServletRequest request) {
		page.setLimit(1000);
		List<String> columns = JSONArray.parseArray(columnEN, String.class);
		columns.add("managerId");
		RestServiceResult<Object> result = new RestServiceResult<Object>();
		try {
			List<Map<String, Object>> data = columnRuleService.getByConditionForPage(columns, null, condition, page,
					filedCode);
			if (!CollectionUtils.isEmpty(data)) {
				Set<Integer> userIds = new HashSet<Integer>();
				for (Map<String, Object> map : data) {
					if (null != map && null != map.get("managerId")) {
						userIds.add(Integer.parseInt(String.valueOf(map.get("managerId"))));
					}
				}
				if (!CollectionUtils.isEmpty(userIds)) {
					data = remoteBaseService.matchUserName(data, new RestServiceResult<List<Map<String, Object>>>(),
							HttpServletHelper.getUserToken(request), userIds, "managerId", "managerName");
					if (RestServiceResult.CODE_SUCCESS != result.getCode()) {
						return result;
					}
				}
			}
			ExcelUtil.downloadExcel(response, data, "字段规则信息", "字段规则信息", columns,
					ResourceColumnRuleFieldsEnum.getOptionalColumns());
			return result;
		} catch (IOException e) {
			result.setCode(RestServiceResult.CODE_UNKNOW);
			result.setMsg("系统异常，请稍后再试！");
			ExceptionLogger.error("字段规则信息导出异常！", e.getMessage(), e);
			return result;
		}
	}

	/**
	 * @api {get} /columnRule/add.json 新增规则
	 * @apiName add
	 * @apiVersion 0.0.1
	 * @apiGroup 字段规则配置
	 * 
	 * @apiParam {String} ruleName 规则名称(必需)
	 * @apiParam {String} ruleDesc 规则描述 (必需)
	 * @apiParam {String} rulePackage 包名 (必需)
	 * @apiParam {String} ruleMethod 方法名 (必需)
	 * 
	 * @apiSuccess {String} code 状态码:1 成功 -1 失败
	 * @apiSuccess {String} msg 错误信息
	 * @apiSuccess {int} count 结果集数据量
	 * @apiSuccess {Object[]} data 结果集
	 *
	 * @apiSuccessExample {json} 成功返回结果
	 *                    {"code":0,"msg":null,"count":0,"data":[{}]}
	 * 
	 */
	@ResponseBody
	@RequestMapping(value = "/add.json")
	public RestServiceResult<Object> add(
			@RequestParam(defaultValue = "", required = true, value = "ruleName") String ruleName,
			@RequestParam(defaultValue = "", required = true, value = "ruleDesc") String ruleDesc,
			@RequestParam(defaultValue = "", required = true, value = "ruleMsg") String ruleMsg,
			@RequestParam(defaultValue = "", required = true, value = "rulePackage") String rulePackage,
			@RequestParam(defaultValue = "", required = true, value = "ruleMethod") String ruleMethod,
			HttpServletRequest request) {
		RestServiceResult<Object> result = new RestServiceResult<Object>();
		// 获取当前用户信息
		RestServiceResult<SysUser> user = remoteBaseService.getCurrentUser(HttpServletHelper.getUserToken(request));
		SysUser userInfo = null;
		if (RestServiceResult.CODE_SUCCESS == user.getCode()) {
			userInfo = user.getData();
			if (null == userInfo || userInfo.getId() <= 0) {
				result.setCode(RestServiceResult.CODE_UNKNOW);
				result.setMsg("系统异常，请稍后再试！");
				ExceptionLogger.error("ColumnRuleController#add", "未获取到当前用户信息！");
				return result;
			}
		} else {
			result.setCode(user.getCode());
			result.setMsg(user.getMsg());
			return result;
		}
		int num = columnRuleService.selectSameName(ruleName);
		Date day = new Date();
		SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd");
		if (num > 0) {
			result.setCode(RestServiceResult.CODE_UNKNOW);
			result.setMsg("存在相同名称字段规则!");
			return result;
		} else {
			columnRuleService.add(ruleName, ruleDesc, rulePackage, ruleMethod, userInfo.getId(), df.format(day),ruleMsg);
		}
		return new RestServiceResult<Object>();
	}

	/**
	 * @api {get} /columnRule/del.json 删除规则
	 * @apiName del
	 * @apiVersion 0.0.1
	 * @apiGroup 字段规则配置
	 * 
	 * @apiParam {String} ids 规则id(必需)
	 * 
	 * @apiSuccess {String} code 状态码:1 成功 -1 失败
	 * @apiSuccess {String} msg 错误信息
	 * @apiSuccess {int} count 结果集数据量
	 * @apiSuccess {Object[]} data 结果集
	 *
	 * @apiSuccessExample {json} 成功返回结果
	 *                    {"code":0,"msg":null,"count":0,"data":[{}]}
	 * 
	 */
	@ResponseBody
	@RequestMapping(value = "/del.json")
	public RestServiceResult<Object> del(@RequestParam(defaultValue = "", required = true, value = "ids") String ids) {
		columnRuleService.del(ids);
		return new RestServiceResult<Object>();
	}

	/**
	 * @api {get} /columnRule/selectOne.json 获取数据
	 * @apiName selectOne
	 * @apiVersion 0.0.1
	 * @apiGroup 字段规则配置
	 * 
	 * @apiParam {String} id 规则id(必需)
	 * 
	 * @apiSuccess {String} code 状态码:1 成功 -1 失败
	 * @apiSuccess {String} msg 错误信息
	 * @apiSuccess {int} count 结果集数据量
	 * @apiSuccess {Object[]} data 结果集
	 *
	 * @apiSuccessExample {json} 成功返回结果
	 *                    {"code":0,"msg":null,"count":1,"data":[{"rule_package":"1222","rule_desc":"122222","rule_name":"1","rule_method":"123","id":22,"time":"2018-04-23","managerName":"超级管理员"}]}
	 * 
	 */
	@ResponseBody
	@RequestMapping("/selectOne.json")
	public RestServiceResult<InspectRule> selectOne(
			@RequestParam(defaultValue = "", required = true, value = "id") int id) {
		InspectRule inspectRule = columnRuleService.select(id);
		return new RestServiceResult<InspectRule>(inspectRule);
	}

	/**
	 * @api {get} /columnRule/modify.json 修改字段规则
	 * @apiName modify
	 * @apiVersion 0.0.1
	 * @apiGroup 字段规则配置
	 * 
	 * @apiParam {int} id 规则id(必需)
	 * @apiParam {String} ruleName 规则名称(必需)
	 * @apiParam {String} ruleDesc 规则描述 (必需)
	 * @apiParam {String} rulePackage 包名 (必需)
	 * @apiParam {String} ruleMethod 方法名 (必需)
	 * 
	 * @apiSuccess {String} code 状态码:1 成功 -1 失败
	 * @apiSuccess {String} msg 错误信息
	 * @apiSuccess {int} count 结果集数据量
	 * @apiSuccess {Object[]} data 结果集
	 *
	 * @apiSuccessExample {json} 成功返回结果
	 *                    {"code":0,"msg":null,"count":0,"data":[{}]}
	 * 
	 */
	@ResponseBody
	@RequestMapping(value = "/modify.json")
	public RestServiceResult<Object> modify(@RequestParam(defaultValue = "", required = true, value = "id") int id,
			@RequestParam(defaultValue = "", required = true, value = "ruleName") String ruleName,
			@RequestParam(defaultValue = "", required = true, value = "ruleDesc") String ruleDesc,
			@RequestParam(defaultValue = "", required = true, value = "ruleMsg") String ruleMsg,
			@RequestParam(defaultValue = "", required = true, value = "rulePackage") String rulePackage,
			@RequestParam(defaultValue = "", required = true, value = "ruleMethod") String ruleMethod,
			HttpServletRequest request) {

		RestServiceResult<Object> result = new RestServiceResult<Object>();
		// 获取当前用户信息
		RestServiceResult<SysUser> user = remoteBaseService.getCurrentUser(HttpServletHelper.getUserToken(request));
		SysUser userInfo = null;
		if (RestServiceResult.CODE_SUCCESS == user.getCode()) {
			userInfo = user.getData();
			if (null == userInfo || userInfo.getId() <= 0) {
				result.setCode(RestServiceResult.CODE_UNKNOW);
				result.setMsg("系统异常，请稍后再试！");
				ExceptionLogger.error("ColumnRuleController#add", "未获取到当前用户信息！");
				return result;
			}
		} else {
			result.setCode(user.getCode());
			result.setMsg(user.getMsg());
			return result;
		}
		Date day = new Date();
		SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd");
		columnRuleService.modify(id, ruleName, ruleDesc, rulePackage, ruleMethod, userInfo.getId(), df.format(day),ruleMsg);
		return new RestServiceResult<Object>();
	}

	/**
	 * @api {get} /columnRule/checkRule.json 校验字段规则
	 * @apiName checkRule
	 * @apiVersion 0.0.1
	 * @apiGroup 字段规则配置
	 * 
	 * @apiParam {int} id 规则id(必需)
	 * @apiParam {String} data 需要检验的数据(必需)
	 * @apiParam {String} extend 扩展 (必需)
	 * 
	 * @apiSuccess {String} code 状态码:1 成功 -1 失败
	 * @apiSuccess {String} msg 错误信息
	 * @apiSuccess {int} count 结果集数据量
	 * @apiSuccess {Object[]} data 结果集
	 *
	 * @apiSuccessExample {json} 成功返回结果
	 *                    {"code":0,"msg":null,"count":0,"data":[{}]}
	 * 
	 */
	@ResponseBody
	@RequestMapping(value = "/checkRule.json")
	public RestServiceResult<Object> checkRule(@RequestParam(defaultValue = "", required = true, value = "id") int id,
			@RequestParam(defaultValue = "", required = true, value = "data") String data,
			@RequestParam(defaultValue = "", required = true, value = "extend") String extend) {
		columnRuleService.checkRule(id, data, extend);
		return new RestServiceResult<Object>();
	}

	/**
	 * 获取字段规则
	 * 
	 * 
	 */
	@IgnoreAuthority
	@ResponseBody
	@RequestMapping(value = "/getColumnRules.json")
	public RestServiceResult<List<InspectRule>> getColumnRules(
			@RequestParam(defaultValue = "", required = true, value = "ruleName") String ruleName) {
		List<InspectRule> columnRules = columnRuleService.getColumnRules(ruleName);
		return new RestServiceResult<List<InspectRule>>(columnRules);
	}

	/**
	 * 获取绑定字段规则的字段
	 *
	 */
	@IgnoreAuthority
	@ResponseBody
	@RequestMapping(value = "/getBindRuleColumns.json")
	public RestServiceResult<List<InspectRule>> getBindRuleColumns(
			@RequestParam(defaultValue = "", required = true, value = "ruleId") String ruleId,
			@RequestParam(defaultValue = "", required = true, value = "resourceTitle") String resourceName, Page page) {

		// 获取当前版本信息，没有则提示
		Integer version = ruleBindingService.selectCurrentContentVersion();
		// if (null == version || version < 0) {
		// throw new ServiceException("没有启用的发布版本");
		// }
		List<InspectRule> bindRuleColumns = columnRuleService.getBindRuleColumns(version, ruleId, resourceName, page);

		return new RestServiceResult<List<InspectRule>>(page.getTotalCount(), bindRuleColumns);
	}
}
